/**
 * Copyright (c) 2017-2020 四川智慧云天 All rights reserved.
 *
 * https://www.sczhyt.cn
 *
 * 版权所有，侵权必究！
 */

package cn.sczhyt.modules.sys.controller;

import cn.sczhyt.modules.sys.dao.SysUserDao;
import cn.sczhyt.modules.sys.dao.SysUserInfoDao;
import cn.sczhyt.modules.sys.entity.SysUserInfoEntity;
import cn.sczhyt.modules.sys.entity.vo.SysUserVo1Entity;
import com.baomidou.mybatisplus.core.metadata.IPage;
import com.tencentcloudapi.common.exception.TencentCloudSDKException;
import cn.sczhyt.common.annotation.SysLog;
import cn.sczhyt.common.utils.*;
import cn.sczhyt.common.validator.Assert;
import cn.sczhyt.common.validator.ValidatorUtils;
import cn.sczhyt.common.validator.group.AddGroup;
import cn.sczhyt.modules.sys.dao.SysMobileCodeDao;
import cn.sczhyt.modules.sys.entity.SysMobileCodeEntity;
import cn.sczhyt.modules.sys.entity.SysUserEntity;
import cn.sczhyt.modules.sys.form.PasswordForm;
import cn.sczhyt.modules.sys.service.SysMobileCodeService;
import cn.sczhyt.modules.sys.service.SysUserRoleService;
import cn.sczhyt.modules.sys.service.SysUserService;
import io.swagger.annotations.Api;
import io.swagger.annotations.ApiOperation;
import org.apache.shiro.authz.annotation.RequiresPermissions;
import org.apache.shiro.crypto.hash.Sha256Hash;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.*;

import java.util.Date;
import java.util.List;

import static cn.sczhyt.common.utils.Constant.SUPER_ADMIN;
import static cn.sczhyt.common.utils.RandomNumberUtils.getSixCode;

/**
 * 系统用户
 *
 * @author Mark sunlightcs@gmail.com
 */
@Api(tags = "系统用户")
@RestController
@RequestMapping("/sys/user")
public class SysUserController extends AbstractController {
	@Autowired
	private SysUserService sysUserService;
	@Autowired
	private SysUserRoleService sysUserRoleService;
	@Autowired
	private SysMobileCodeDao mobileCodeDao;
	@Autowired
	private SysMobileCodeService sysMobileCodeService;
	@Autowired
	private SysUserInfoDao userInfoDao;
	/**
	 * 管理员列表
	 */
	@ApiOperation("管理员列表")
	@PostMapping("/list/admin")
	//@RequiresPermissions("sys:user:list")
	public R list(@RequestParam(defaultValue = "1") Integer page,
				  @RequestParam(defaultValue = "20") Integer limit,
				  @RequestBody(required = false) SysUserVo1Entity userEntity){

		IPage<SysUserEntity> list = sysUserService.list(page, limit, userEntity);

		return R.ok().put("data",list);
	}
	/**
	 * 代表团列表
	 */
	@ApiOperation("代表团列表")
	@PostMapping("/list/delegation")
	//@RequiresPermissions("sys:user:list")
	public R listByRoleId(@RequestParam(defaultValue = "1") Integer page,
				  @RequestParam(defaultValue = "20") Integer limit,
				  @RequestBody(required = false) SysUserVo1Entity userEntity){

		IPage<SysUserEntity> list = sysUserService.listByRoleId(page, limit, userEntity);

		return R.ok().put("data",list);
	}

	/**
	 * 获取登录的用户安全信息
	 */
	@ApiOperation("获取登录的用户安全信息")
	@GetMapping("/info")
	public R info(){
		return R.ok().put("user", getUser());
	}

	/**
	 * 获取登录的用户详情信息
	 */
	@ApiOperation("获取登录的用户详情信息")
	@GetMapping("/get/info")
	public R getInfo(){
		return R.ok().put("user", getUser());
	}

	/**
	 * 找回密码的短信验证
	 * @param form
	 * @return
	 */
	@ApiOperation("找回密码的短信验证")
	@PostMapping("/forget/password/smsCode")
	public R forgetPasswordSmsCode(@RequestBody PasswordForm form) throws TencentCloudSDKException {
		Assert.isBlank(form.getMobile(),"请输入手机号码");
		String mobile = form.getMobile();
		SysUserEntity sysUserEntity = sysUserService.queryByMobile(mobile);
		if (sysUserEntity == null) {
			return R.error(1001,"该手机号未绑定用户");
		}
		// 获取手机号，并发送短信
		String[] phoneNumbers = {"+86"+form.getMobile()};

		// 模板ID,密码重置的模板ID
		String ID = "681631";
		// 随机六位数
		String code = String.valueOf(getSixCode());
		String codeTime = "5";//有效期5分钟
		// 放入模板需要的参数
		String[] param = {code,codeTime};
		// 调用发送短信的工具
		SmsUtils.sendSms(phoneNumbers, ID, param);
		//保存验证码
		SysMobileCodeEntity sysMobileCodeEntity = new SysMobileCodeEntity();
		sysMobileCodeEntity.setMobile(form.getMobile());
		sysMobileCodeEntity.setMsgCode(code);
		sysMobileCodeEntity.setExpireTime(DateUtils.addDateMinutes(new Date(), 5));//设置五分钟过期
		if (mobileCodeDao.selectById(form.getMobile()) == null) {
			mobileCodeDao.insert(sysMobileCodeEntity);
		}else {
			mobileCodeDao.updateById(sysMobileCodeEntity);
		}

		return R.ok();
	}

	/**
	 * 对比手机号验证码
	 */
	@ApiOperation("对比手机号验证码")
	@PostMapping("/checkCode")
	public R checkCode(@RequestBody PasswordForm form){

		//判断验证码是否正确
		return sysMobileCodeService.checkCode(form.getMobile(), form.getMsgCode());

	}

	/**
	 * 用户自己重置密码
	 */
	@ApiOperation("用户自己重置密码")
	@PostMapping("/reset/password")
	public R resetPassword(@RequestBody PasswordForm form){
		SysUserEntity user = sysUserService.queryByMobile(form.getMobile());

		// 账号不存在
		if (user == null) {
			return R.error(202, "该手机号未绑定用户");
		}

		//判断验证码是否正确
		Boolean b = sysMobileCodeService.validate(form.getMobile(), form.getMsgCode());
		if (!b){
			return R.error(1002,"验证码不正确，请重新输入");
		}
		// 账号锁定
		if (user.getStatus() == 0) {
			return R.error(204, "账号已被锁定,请联系管理员");
		}
		//sha256加密
		String newPassword = new Sha256Hash(form.getNewPassword(), user.getSalt()).toHex();

		sysUserService.updatePassword(user.getUserId(),user.getPassword(),newPassword);
		return R.ok();
	}

	/**
	 * 管理员重置用户的密码
	 */
	@ApiOperation("管理员重置用户的密码")
	@PostMapping("/admin/reset/password")
	public R adminResetPassword(@RequestParam String userId){

		SysUserEntity user = sysUserService.queryByUserId(userId);
		// 账号不存在
		if (user == null) {
			return R.error(202, "用户不存在");
		}

		//sha256加密
		String newPassword = new Sha256Hash("666666", user.getSalt()).toHex();

		boolean b = sysUserService.adminResetPassword(user.getUserId(), newPassword);
		if (b) {
			return R.ok();
		}

		return R.error(500,"系统维护中，暂时不能重置密码");
	}
	/**
	 * 修改登录用户密码
	 */
	@ApiOperation("修改登录用户密码")
	@SysLog("修改密码")
	@PostMapping("/password")
	public R password(@RequestBody PasswordForm form){
		Assert.isBlank(form.getNewPassword(), "新密码不为能空");

		//sha256加密
		String password = new Sha256Hash(form.getPassword(), getUser().getSalt()).toHex();
		//sha256加密
		String newPassword = new Sha256Hash(form.getNewPassword(), getUser().getSalt()).toHex();

		//更新密码
		boolean flag = sysUserService.updatePassword(getUserId(), password, newPassword);

		if(!flag){
			return R.error("原密码不正确");
		}
		return R.ok();
	}

	/**
	 * 账号禁用或启用
	 */
	@ApiOperation("账号禁用或启用")
	@PostMapping("/status/change")
	public R statusChange(@RequestParam String userId){

		return sysUserService.updateStatus(userId);

	}


	/**
	 * 用户信息
	 */
	@ApiOperation("用户信息")
	@GetMapping("/info/{userId}")
	@RequiresPermissions("sys:user:info")
	public R info(@PathVariable("userId") String userId){
		SysUserEntity user = sysUserService.getById(userId);

		//获取用户所属的角色列表
		List<String> roleIdList = sysUserRoleService.queryRoleIdList(userId);
		user.setRoleIdList(roleIdList);

		SysUserInfoEntity userInfo = userInfoDao.selectByUserId(userId);

		return R.ok().put("user", user).put("userInfo",userInfo);
	}


	/**
	 * 保存用户,管理员保存
	 */
	@ApiOperation("保存用户")
	@SysLog("保存用户")
	@PostMapping("/save/admin")
	@RequiresPermissions("sys:user:save")
	public R saveToAdmin(@RequestBody SysUserVo1Entity user){
		System.out.println(user.toString());
		ValidatorUtils.validateEntity(user, AddGroup.class);

		user.setCreateUserId(getUserId());
		sysUserService.saveUserToAdmin(user);

		return R.ok();
	}
	/**
	 * 保存用户,代表团
	 */
	@ApiOperation("保存用户")
	@SysLog("保存用户")
	@PostMapping("/save/delegation")
	//@RequiresPermissions("sys:user:save")
	public R save(@RequestBody SysUserVo1Entity user){

		ValidatorUtils.validateEntity(user, AddGroup.class);

		user.setCreateUserId(getUserId());
		sysUserService.saveUserToDelegation(user);

		return R.ok();
	}

	/**
	 * 修改用户
	 */
	@ApiOperation("修改用户")
	@SysLog("修改用户")
	@PostMapping("/update")
	@RequiresPermissions("sys:user:update")
	public R update(@RequestBody SysUserVo1Entity user){

		user.setCreateUserId(getUserId());

		SysUserEntity userEntity = new SysUserEntity();
		BeanUtils.copyProperties(user,userEntity);

		sysUserService.update(userEntity);

		return R.ok();
	}

	/**
	 * 删除用户
	 */
	@ApiOperation("删除用户")
	@SysLog("删除用户")
	@PostMapping("/delete")
	@RequiresPermissions("sys:user:delete")
	public R delete(@RequestParam String userId){
		if(userId.equals(SUPER_ADMIN)){
			return R.error("系统管理员不能删除");
		}

		if(userId.equals(getUserId())){
			return R.error("当前用户不能删除");
		}

		sysUserService.delete(userId);

		return R.ok();
	}
}
